-- slime_star_damage
-- create by zhuangsl
-- 技能：对场上随机怪物造成n次伤害
-- 配置：slime_star_damage(11, 450, 150，3)：冈布奥专属技能11，对随机怪物造成3次伤害，单次伤害 = attack * (0.450 + 0.15 * level)
return {
    apply = function(source, target, skillId, round, para, extra)
        -- 专属技能等级
        local level;
        extra = extra or {};
        if extra["level"] then
            level = tonumber(extra["level"]);
        else
            local prop = PropM.combine(source, "gain_slime_skill", para[1]);
            level = PropM.apply(prop, 0);
        end

        -- 威力
        local base = para[2];
        local force = para[3];

        -- 攻击方的攻击
        local attack = source:getAttack();

        -- 伤害
        local damage = math.modf(attack * (base + force * level) / 1000);

        -- 斯巴达专属加成
        local prop = PropM.combine(source, "battle_cry", 1);
        if prop[3] > 0 then
            -- 触发特技发动事件
            EventMgr.fire(event.SPECIAL_SKILL_TRIGGER, { propId = prop[1] });
        end
        damage = PropM.apply(prop, damage);

        -- 遍历所有的怪
        local ret = {};

        -- 取出场上已翻开且未死亡的怪物
        for p = 1, DUNGEON_WIDTH * DUNGEON_HEIGHT do
            local grid = DungeonM.getGridByPos(p);

            -- 是未死亡的怪物
            if  grid:isOpened() and
                grid:isMonster() and
                not grid.monster:isDead() then
                table.insert(ret, grid.monster);
            end
        end

        -- 打击目标
        local count = para[4];
        -- 连携附带穿击炮效果，个数加
        prop = PropM.combine(source, "even_carrying", "strike");
        if FormulaM.invoke("CAN_EVEN_CARRYING", skillId) and prop[3] > 0 then
            count = count + prop[3];
        end

        local posList = {};
        for index = 1, count do
            local num = #ret;
            if num == 0 then
                break;
            end
            -- 随机选一个进行打击
            local rand = DungeonM.getRandSeed("slime_star_damage") % num;
            local monster = ret[rand + 1];

            -- 加入受打击位置列表
            table.insert(posList, monster:getPos());

            -- 需要UI延迟
            extra["delay_time"] = 2;

            -- 增加命中动作
            if SkillM.getSequence(monster) == nil then
                SkillM.getSequenceList()[monster] = CastSequence.create(source, monster, skillId);
            end
            SkillM.getSequence(monster):hit(source, monster, skillId);
            -- 受创
            CombatM.receiveDamage(source, monster, damage, skillId, extra);
            
            -- 连携附带粉碎效果
            prop = PropM.combine(source, "even_carrying", "smash");
            if FormulaM.invoke("CAN_EVEN_CARRYING", skillId) and prop[3] ~= 0 and not monster:isDead() then
                local effectRound = round + prop[4] + 1;
                local condition = {
                    ["value"] = prop[3],
                    ["end_round"] = effectRound,
                };

                CombatStatusM.applyStatus(monster, prop[2], condition);
            end

            -- 如果目标已经死了，从待打击列表中移除
            if monster:isDead() then
                table.removeItem(ret, monster);
                -- 如果全死了
                if #ret == 0 then
                    break;
                end
            end
        end

        -- 抛出使用技能事件
        if #posList > 0 then
            EventMgr.fire(event.SLIME_STAR_DAMAGE, { ["pos_list"] = posList, });
        end

        -- 作用目标
        return ret;
    end,

    parse = function(desc)
        local arr = string.explode(desc, ",");
        return { tonumber(arr[1]), tonumber(arr[2]), tonumber(arr[3]), tonumber(arr[4])};
    end,

    -- 解析技能描述
    parseDesc = function(source, skillId, desc, para)
        -- 专属技能等级
        local prop = PropM.combine(source, "gain_slime_skill", para[1]);
        local level = PropM.apply(prop, 0);

        -- 威力
        local base = para[2];
        local force = para[3];

        -- 攻击方的攻击
        local attack = source:getAttack();

        -- 伤害
        local damage = math.modf(attack * (base + force * level) / 1000);

        -- 斯巴达专属加成
        prop = PropM.combine(source, "battle_cry", 1);
        damage = PropM.apply(prop, damage);

        -- 数量
        local count = para[4];
        -- 连携附带穿击炮效果，个数加
        prop = PropM.combine(source, "even_carrying", "strike");
        if FormulaM.invoke("CAN_EVEN_CARRYING", skillId) and prop[3] > 0 then
            count = count + prop[3];
        end

        desc = string.gsub(desc, "{count}", count);
        desc = string.gsub(desc, "{damage}", damage);

        return desc;
    end,
};
